package com.commerce.product.interceptor;

import com.commerce.common.utils.Result;
import com.commerce.product.service.AntiSpamService;
import com.fasterxml.jackson.databind.ObjectMapper;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;

import java.io.IOException;
import java.io.PrintWriter;

/**
 * 防刷拦截器
 */
@Slf4j
@Component
public class AntiSpamInterceptor implements HandlerInterceptor {

    @Autowired
    private AntiSpamService antiSpamService;

    @Autowired
    private ObjectMapper objectMapper;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        // 只对秒杀相关接口进行防刷检查
        String requestURI = request.getRequestURI();
        if (!isFlashSaleRequest(requestURI)) {
            return true;
        }

        // 获取用户信息
        Long userId = getUserId(request);
        String ip = getClientIp(request);
        String userAgent = request.getHeader("User-Agent");

        // 如果无法获取用户ID，直接拒绝
        if (userId == null) {
            writeErrorResponse(response, "用户未登录");
            return false;
        }

        // 执行防刷检查
        AntiSpamService.AntiSpamResult result = antiSpamService.comprehensiveCheck(userId, ip, userAgent);
        
        if (!result.isAllowed()) {
            log.warn("防刷检查失败: userId={}, ip={}, reason={}", userId, ip, result.getReason());
            writeErrorResponse(response, result.getReason());
            return false;
        }

        // 将用户信息添加到请求属性中，供后续使用
        request.setAttribute("userId", userId);
        request.setAttribute("userIp", ip);
        request.setAttribute("userAgent", userAgent);

        return true;
    }

    /**
     * 判断是否为秒杀相关请求
     */
    private boolean isFlashSaleRequest(String requestURI) {
        return requestURI.contains("/flash-sale/") || 
               requestURI.contains("/flash_sale/") ||
               requestURI.endsWith("/purchase") ||
               requestURI.endsWith("/buy");
    }

    /**
     * 获取用户ID
     */
    private Long getUserId(HttpServletRequest request) {
        try {
            // 从请求头获取用户ID
            String userIdHeader = request.getHeader("X-User-Id");
            if (userIdHeader != null) {
                return Long.valueOf(userIdHeader);
            }

            // 从请求参数获取用户ID
            String userIdParam = request.getParameter("userId");
            if (userIdParam != null) {
                return Long.valueOf(userIdParam);
            }

            // 这里可以添加从JWT token中解析用户ID的逻辑
            // String token = request.getHeader("Authorization");
            // if (token != null) {
            //     return parseUserIdFromToken(token);
            // }

            return null;
        } catch (Exception e) {
            log.error("获取用户ID失败: {}", e.getMessage());
            return null;
        }
    }

    /**
     * 获取客户端真实IP
     */
    private String getClientIp(HttpServletRequest request) {
        String ip = request.getHeader("X-Forwarded-For");
        if (ip == null || ip.isEmpty() || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("Proxy-Client-IP");
        }
        if (ip == null || ip.isEmpty() || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("WL-Proxy-Client-IP");
        }
        if (ip == null || ip.isEmpty() || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_CLIENT_IP");
        }
        if (ip == null || ip.isEmpty() || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getHeader("HTTP_X_FORWARDED_FOR");
        }
        if (ip == null || ip.isEmpty() || "unknown".equalsIgnoreCase(ip)) {
            ip = request.getRemoteAddr();
        }
        
        // 如果是多级代理，取第一个IP
        if (ip != null && ip.contains(",")) {
            ip = ip.split(",")[0].trim();
        }
        
        return ip;
    }

    /**
     * 写入错误响应
     */
    private void writeErrorResponse(HttpServletResponse response, String message) throws IOException {
        response.setStatus(429); // HTTP 429 Too Many Requests
        response.setContentType("application/json;charset=UTF-8");

        Result<Object> result = Result.error(429, message);
        String jsonResponse = objectMapper.writeValueAsString(result);

        try (PrintWriter writer = response.getWriter()) {
            writer.write(jsonResponse);
            writer.flush();
        }
    }
}
